#include "MainWindow.h"
#include "Application.h"
#include "GeneticsEngine.h"

MainWindow::MainWindow()
: m_pPlayButton(NULL)
, m_pPauseButton(NULL)
, m_pRestartButton(NULL)
, m_pDebugCheck(NULL)
, m_pFastestLap(NULL)
, m_pAverageLap(NULL)
, m_pSlowestLap(NULL)
, m_pEvolutionCount(NULL)
, m_pTitle(NULL)
, m_pTitle2(NULL)
, m_pEvolutionCombo(NULL)
, m_pEvolutionText(NULL)
, m_pEvolution2Combo(NULL)
, m_pEvolution2Text(NULL)
, m_pParent1Combo(NULL)
, m_pParent1Text(NULL)
, m_pParent2Combo(NULL)
, m_pParent2Text(NULL)
, m_pPenaltyCombo(NULL)
, m_pPenaltyText(NULL)
, m_pTimeoutCombo(NULL)
, m_pTimeoutText(NULL)
, m_pNumAgentsCombo(NULL)
, m_pNumAgentsText(NULL)
{
}
MainWindow::~MainWindow()
{
	if(m_pPlayButton)
	{
		delete m_pPlayButton;
		m_pPlayButton = NULL;
	}
	if(m_pPauseButton)
	{
		delete m_pPauseButton;
		m_pPauseButton = NULL;
	}
	if(m_pRestartButton)
	{
		delete m_pRestartButton;
		m_pRestartButton = NULL;
	}
	if(m_pDebugCheck)
	{
		delete m_pDebugCheck;
		m_pDebugCheck = NULL;
	}
	if(m_pFastestLap)
	{
		delete m_pFastestLap;
		m_pFastestLap = NULL;
	}
	if(m_pAverageLap)
	{
		delete m_pAverageLap;
		m_pAverageLap = NULL;
	}
	if(m_pSlowestLap)
	{
		delete m_pSlowestLap;
		m_pSlowestLap = NULL;
	}
	if(m_pEvolutionCount)
	{
		delete m_pEvolutionCount;
		m_pEvolutionCount = NULL;
	}
	if(m_pTitle)
	{
		delete m_pTitle;
		m_pTitle = NULL;
	}
	if(m_pTitle2)
	{
		delete m_pTitle2;
		m_pTitle2 = NULL;
	}
	if(m_pEvolutionCombo)
	{
		delete m_pEvolutionCombo;
		m_pEvolutionCombo = NULL;
	}
	if(m_pEvolutionText)
	{
		delete m_pEvolutionText;
		m_pEvolutionText = NULL;
	}
	if(m_pEvolution2Combo)
	{
		delete m_pEvolution2Combo;
		m_pEvolution2Combo = NULL;
	}
	if(m_pEvolution2Text)
	{
		delete m_pEvolution2Text;
		m_pEvolution2Text = NULL;
	}
	if(m_pParent1Combo)
	{
		delete m_pParent1Combo;
		m_pParent1Combo = NULL;
	}
	if(m_pParent1Text)
	{
		delete m_pParent1Text;
		m_pParent1Text = NULL;
	}
	if(m_pParent2Combo)
	{
		delete m_pParent2Combo;
		m_pParent2Combo = NULL;
	}
	if(m_pParent2Text)
	{
		delete m_pParent2Text;
		m_pParent2Text = NULL;
	}
	if(m_pPenaltyCombo)
	{
		delete m_pPenaltyCombo;
		m_pPenaltyCombo = NULL;
	}
	if(m_pPenaltyText)
	{
		delete m_pPenaltyText;
		m_pPenaltyText = NULL;
	}
	if(m_pTimeoutCombo)
	{
		delete m_pTimeoutCombo;
		m_pTimeoutCombo = NULL;
	}
	if(m_pTimeoutText)
	{
		delete m_pTimeoutText;
		m_pTimeoutText = NULL;
	}
	if(m_pNumAgentsCombo)
	{
		delete m_pNumAgentsCombo;
		m_pNumAgentsCombo = NULL;
	}
	if(m_pNumAgentsText)
	{
		delete m_pNumAgentsText;
		m_pNumAgentsText = NULL;
	}
}

bool MainWindow::Setup(HWND a_parent, HINSTANCE a_hInst, int a_xPos, int a_yPos, int a_width, int a_height, char* a_pWindowName, char* a_pClassName, DWORD a_style)
{
	WNDCLASS wndClass;
	ZeroMemory(&wndClass, sizeof(WNDCLASS));

	wndClass.cbClsExtra = NULL;
	wndClass.cbWndExtra = sizeof(Controller*);
	wndClass.hbrBackground = (HBRUSH)GetStockObject(LTGRAY_BRUSH);
	wndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
	wndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
	wndClass.hInstance = a_hInst;
	wndClass.lpfnWndProc = Controller::WndProc;
	wndClass.lpszMenuName = NULL;
	wndClass.style = CS_DROPSHADOW;
	wndClass.lpszClassName = a_pClassName;

	if(!RegisterClass(&wndClass))
	{
		return false;
	}

	m_hWnd = CreateWindowEx(WS_EX_CONTROLPARENT, a_pClassName, a_pWindowName, a_style, a_xPos, a_yPos, a_width, a_height, a_parent, NULL, a_hInst, (LPVOID)this);
	if(m_hWnd == NULL)
	{
		return false;
	}
	UpdateWindow(m_hWnd);
	ShowWindow(m_hWnd, SW_SHOW);

	//m_pPlayButton = new Button();
	//m_pPlayButton->Setup(m_hWnd, a_hInst, 15, 520, 50, 30, "Play", "Play the simulation.");

	//m_pPauseButton = new Button();
	//m_pPauseButton->Setup(m_hWnd, a_hInst, 75, 520, 50, 30, "Pause", "Pause the simulation.");

	//m_pRestartButton = new Button();
	//m_pRestartButton->Setup(m_hWnd, a_hInst, 135, 520, 50, 30, "Restart", "Restart the simulation.");

	//Sector one
	m_pTitle = new StaticText();
	m_pTitle->Setup(m_hWnd, a_hInst, 20, 10, 155, 15, "Debug Info");

	m_pFastestLap = new EditCombo();
	m_pFastestLap->Setup(m_hWnd, a_hInst, 20, 30, 100, 15, 50, 15, "Fastest Lap: ");
	m_pFastestLap->GetEdit()->SetText("0");
	Edit_Enable(m_pFastestLap->GetEdit()->GetHWND(), false);

	//m_pAverageLap = new EditCombo();
	//m_pAverageLap->Setup(m_hWnd, a_hInst, 20, 50, 100, 15, 50, 15, "Average Lap: ");
	//m_pAverageLap->GetEdit()->SetText("0");
	//Edit_Enable(m_pAverageLap->GetEdit()->GetHWND(), false);
	
	m_pSlowestLap = new EditCombo();
	m_pSlowestLap->Setup(m_hWnd, a_hInst, 20, 50, 100, 15, 50, 15, "Slowest Lap: ");
	m_pSlowestLap->GetEdit()->SetText("0");
	Edit_Enable(m_pSlowestLap->GetEdit()->GetHWND(), false);

	m_pEvolutionCount = new EditCombo();
	m_pEvolutionCount->Setup(m_hWnd, a_hInst, 20, 70, 100, 15, 50, 15, "Evolution Count: ");
	m_pEvolutionCount->GetEdit()->SetText("0");
	Edit_Enable(m_pEvolutionCount->GetEdit()->GetHWND(), false);

	//Sector one
	m_pTitle2 = new StaticText();
	m_pTitle2->Setup(m_hWnd, a_hInst, 20, 140, 155, 15, "Input Data");

	//m_pEvolutionCombo = new ComboBox();
	//const char* cb_items[] = {"x1","x3","x5","x20","x100","x1000","x10000"};
	//m_pEvolutionCombo->Setup(m_hWnd, a_hInst, 120, 140, 70, 150, cb_items, 7);
	//m_pEvolutionCombo->SetSelection(0);

	//m_pEvolutionText = new StaticText();
	//m_pEvolutionText ->Setup(m_hWnd, a_hInst, 20, 144, 95, 15, "Evolution Speed: ");

	m_pEvolution2Combo = new ComboBox();
	const char* cb_items1[] = {"1","3","5","10","20","50","200"};
	m_pEvolution2Combo->Setup(m_hWnd, a_hInst, 120, 170, 70, 150, cb_items1, 7);
	m_pEvolution2Combo->SetSelection(0);

	m_pEvolution2Text = new StaticText();
	m_pEvolution2Text ->Setup(m_hWnd, a_hInst, 20, 174, 95, 15, "# Per Render: ");

	m_pParent1Combo = new ComboBox();
	const char* cb_items2[] = {"0","25","50","75","100"};
	m_pParent1Combo->Setup(m_hWnd, a_hInst, 120, 200, 70, 150, cb_items2, 5);
	m_pParent1Combo->SetSelection(2);

	m_pParent1Text = new StaticText();
	m_pParent1Text->Setup(m_hWnd, a_hInst, 20, 204, 95, 15, "Father Weight: ");

	m_pParent2Combo = new ComboBox();
	const char* cb_items3[] = {"0","25","50","75","100"};
	m_pParent2Combo->Setup(m_hWnd, a_hInst, 120, 230, 70, 150, cb_items3, 5);
	m_pParent2Combo->SetSelection(2);

	m_pParent2Text = new StaticText();
	m_pParent2Text->Setup(m_hWnd, a_hInst, 20, 234, 95, 15, "Mother Weight: ");

	/*m_pPenaltyCombo = new ComboBox();
	const char* cb_items4[] = {"2","4","6","8"};
	m_pPenaltyCombo->Setup(m_hWnd, a_hInst, 120, 260, 70, 150, cb_items4, 4);
	m_pPenaltyCombo->SetSelection(2);

	m_pPenaltyText = new StaticText();
	m_pPenaltyText->Setup(m_hWnd, a_hInst, 20, 264, 95, 15, "Timeout Value: ");*/

	m_pPenaltyCombo = new ComboBox();
	const char* cb_items5[] = {"2","4","6","8"};
	m_pPenaltyCombo->Setup(m_hWnd, a_hInst, 120, 260, 70, 150, cb_items5, 4);
	m_pPenaltyCombo->SetSelection(0);

	m_pPenaltyText = new StaticText();
	m_pPenaltyText->Setup(m_hWnd, a_hInst, 20, 264, 95, 15, "Off-Track Penalty: ");

	m_pNumAgentsCombo = new ComboBox();
	const char* cb_items6[] = {"25","50","75","100","200","500"};
	m_pNumAgentsCombo->Setup(m_hWnd, a_hInst, 120, 290, 70, 150, cb_items6, 6);
	m_pNumAgentsCombo->SetSelection(3);

	m_pNumAgentsText = new StaticText();
	m_pNumAgentsText->Setup(m_hWnd, a_hInst, 20, 294, 95, 15, "Agents Number: ");
	
	m_pDebugCheck = new CheckBox();
	m_pDebugCheck->Setup(m_hWnd, a_hInst, 20, 354, 150, 20, "Enable Debug Dump", "Enable or Disable dumping debug information to a log file.");

	return true;
}

void MainWindow::Update()
{
	if(m_pDebugCheck->IsChecked())
	{
		Application::GetInstance().GetGeneticsEngine()->EnableDebugOutput(true);
	}
	else
	{
		Application::GetInstance().GetGeneticsEngine()->EnableDebugOutput(false);
	}
}
void MainWindow::Activate(WPARAM a_wParam)
{
}
void MainWindow::Close()
{
	PostQuitMessage(0);
}
void MainWindow::Destroy()
{
	PostQuitMessage(0);
}
void MainWindow::Size(int a_w, int a_h, LPARAM a_lParam)
{
}
void MainWindow::Command(int a_id, int a_cmd, LPARAM a_msg)
{
	if(a_cmd == CBN_CLOSEUP)
	{
		if(CompareHandles((HWND)a_msg, m_pNumAgentsCombo->GetHWND()))
		{
			Application::GetInstance().GetGeneticsEngine()->SetMaxChildren(atoi(m_pNumAgentsCombo->GetSelection()));
		}
		/*else if(CompareHandles((HWND)a_msg, m_pEvolutionCombo->GetHWND()))
		{
			Application::GetInstance().GetGeneticsEngine()->SetCarSpeed(atof(m_pEvolutionCombo->GetSelection()));
		}*/
		else if(CompareHandles((HWND)a_msg, m_pEvolution2Combo->GetHWND()))
		{
			Application::GetInstance().GetGeneticsEngine()->SetEvolutionsPer(atoi(m_pEvolution2Combo->GetSelection()));
		}
		else if(CompareHandles((HWND)a_msg, m_pPenaltyCombo->GetHWND()))
		{
			Application::GetInstance().GetGeneticsEngine()->SetOffTrackPenalty(atof(m_pPenaltyCombo->GetSelection()));
		}
		/*else if(CompareHandles((HWND)a_msg, m_pTimeoutCombo->GetHWND()))
		{
			Application::GetInstance().GetGeneticsEngine()->SetTimeout(atof(m_pTimeoutCombo->GetSelection()));
		}*/
		else if(CompareHandles((HWND)a_msg, m_pParent1Combo->GetHWND()))
		{
			int sel = m_pParent1Combo->GetSelectionInt();
			m_pParent2Combo->SetSelection(4-sel);
			Application::GetInstance().GetGeneticsEngine()->ApplyWeights(atof(m_pParent1Combo->GetSelection()),atof(m_pParent2Combo->GetSelection()));
		}
		else if(CompareHandles((HWND)a_msg, m_pParent2Combo->GetHWND()))
		{
			int sel = m_pParent2Combo->GetSelectionInt();
			m_pParent1Combo->SetSelection(4-sel);
			Application::GetInstance().GetGeneticsEngine()->ApplyWeights(atof(m_pParent1Combo->GetSelection()),atof(m_pParent2Combo->GetSelection()));
		}
	}
}
void MainWindow::AfterMessages()
{
}
void MainWindow::ContextMenu(HWND a_hWnd, int a_x, int a_y)
{
}
void MainWindow::RButtonDown(WPARAM a_wParam, int a_x, int a_y)
{
}
void MainWindow::KeyDown(HWND a_hWnd, WPARAM a_wParam)
{
	
}
void MainWindow::ButtonPress(HWND a_hWnd)
{
	/*if(CompareHandles(a_hWnd, m_pPlayButton->GetHandle()))
	{
		Application::GetInstance().GetGeneticsEngine()->Pause(false);
	}
	if(CompareHandles(a_hWnd, m_pPauseButton->GetHandle()))
	{
		Application::GetInstance().GetGeneticsEngine()->Pause(true);
	}
	if(CompareHandles(a_hWnd, m_pRestartButton->GetHandle()))
	{
		Application::GetInstance().GetGeneticsEngine()->Reset();
	}*/
}
EditCombo* MainWindow::GetEvolutionCount() const
{
	return m_pEvolutionCount;
}
EditCombo* MainWindow::GetFastestLap() const
{
	return m_pFastestLap;
}
EditCombo* MainWindow::GetAverageLap() const
{
	return m_pAverageLap;
}
EditCombo* MainWindow::GetSlowestLap() const
{
	return m_pSlowestLap;
}